package dao;

import java.io.File;
import java.io.IOException;
import java.net.MalformedURLException;
import java.net.URL;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;

import parsers.CommonMethods;
import parsers.lectureRoom.BuildingsParser;
import parsers.lectureRoom.LectureRoomParser;
import parsers.lectureRoom.LectureRoomsParser;

import model.lectureRoom.Building;
import model.lectureRoom.LectureRoom;

public class LectureRoomDAO 
{
	private static Map<String, Building> buildingsCP = new HashMap<String, Building>();
	private static Map<String, Building> buildingsWithLectureRoomsCP = new HashMap<String, Building>();
	private static Map<String, LectureRoom> lectureRoomsScheduleCP = new HashMap<String, LectureRoom>();
	
	private static String currentDate = util.Utilities.getDateTime();
	
	private static String[] file = new String[] {makeFileName("buiCP"), makeFileName("bwlCP"), makeFileName("lrsCP")};
	
	private long startTime;
	
	@SuppressWarnings("unchecked")
	public LectureRoomDAO()
	{
		startTime();
		System.out.print("Initialising LectureRoom->Buildings: ");
		if( (new File(file[0])).exists() )
		{
			System.out.print("(find serialized file " + file[0] + ") ");
			buildingsCP = (Map<String, Building>) util.Utilities.deserialize(file[0]);
		}
		else
		{
			initBuildings();
		}
		System.out.println(countTime() + " ms");
		
		/////////////////////////////////////////////
		
		startTime();
		System.out.print("Initialising LectureRoom->LectureRooms: ");
		if( (new File(file[1])).exists() )
		{
			System.out.print("(find serialized file " + file[1] + ") ");
			buildingsWithLectureRoomsCP = (Map<String, Building>) util.Utilities.deserialize(file[1]);
		}
		else
		{
			initLectureRooms();
		}
		System.out.println(countTime() + " ms");
		
		/////////////////////////////////////////////
		
		startTime();
		System.out.print("Initialising LectureRoom->LectureRoomsSchedule: ");
		if( (new File(file[2])).exists() )
		{
			System.out.print("(find serialized file " + file[2] + ") ");
			lectureRoomsScheduleCP = (Map<String, LectureRoom>) util.Utilities.deserialize(file[2]);
		}
		else
		{
			initLectureRoomsSchedule();
		}
		System.out.println(countTime() + " ms");
	}
	
	private static String makeFileName(String name)
	{
		return Linker.path + LectureRoomDAO.class.getName() + name + currentDate + ".jsr";
	}
	
	public static void serialize()
	{
		if( !(new File(file[0])).exists() )
		{
			util.Utilities.serialize(buildingsCP, file[0]);
		}
		
		if( !(new File(file[1])).exists() )
		{
			util.Utilities.serialize(buildingsWithLectureRoomsCP, file[1]);
		}
		
		if( !(new File(file[2])).exists() )
		{
			util.Utilities.serialize(lectureRoomsScheduleCP, file[2]);
		}
	}
	
	private void initBuildings()
	{
		BuildingsParser bp = new BuildingsParser();
		ArrayList<Building> buildings = null;
		
		try
		{
			buildings = bp.parse(new URL("http://plan.uz.zgora.pl/sale_lista_budynkow.php?pTyp=P"));
			
			for (int i = 0; i < buildings.size(); i++)
			{
				buildingsCP.put(buildings.get(i).getId(), buildings.get(i));
			}
		} 
		catch (MalformedURLException e)
		{
			e.printStackTrace();
		} 
		catch (IOException e)
		{
			e.printStackTrace();
		}
	}
	
	private void initLectureRooms()
	{
		Iterator<Building> buildings = buildingsCP.values().iterator();
		while(buildings.hasNext())
		{
			Building building = buildings.next();
			Building buil = new Building(building.getName(), building.getDescription(), building.getAddress());
			buil.setLink(CommonMethods.parseLink(building.getLink()));
			buil.setId(building.getId());
			
			LectureRoomsParser lrp = new LectureRoomsParser(buil);
			
			try
			{
				lrp.parse(true);
				buildingsWithLectureRoomsCP.put(buil.getId(), buil);
			} 
			catch (IOException e)
			{
				e.printStackTrace();
			}
		}
	}
	
	private void initLectureRoomsSchedule()
	{
		Iterator<Building> buildings = buildingsWithLectureRoomsCP.values().iterator();
		while(buildings.hasNext())
		{
			Building building = buildings.next();
			ArrayList<LectureRoom> lectureRooms = building.getLectureRooms();
			
			for (int i = 0; i < lectureRooms.size(); i++)
			{
				LectureRoom lectureRoom = new LectureRoom(lectureRooms.get(i).getName(), lectureRooms.get(i).getCapacity(), lectureRooms.get(i).getType(), lectureRooms.get(i).getUnit());
				lectureRoom.setId(lectureRooms.get(i).getId());
				lectureRoom.setLink(CommonMethods.parseLink(lectureRooms.get(i).getLink()));
				
				try
				{
					LectureRoomParser lrp = new LectureRoomParser(lectureRoom);
					lrp.parse(true);
					lectureRoomsScheduleCP.put(lectureRoom.getId(), lectureRoom);
				} 
				catch (IOException e)
				{
					e.printStackTrace();
				}
			}
		}
	}

	public static Map<String, Building> getBuildingsCP()
	{
		return buildingsCP;
	}

	public static Map<String, Building> getBuildingsWithLectureRoomsCP()
	{
		return buildingsWithLectureRoomsCP;
	}

	public static Map<String, LectureRoom> getLectureRoomsScheduleCP()
	{
		return lectureRoomsScheduleCP;
	}

	private void startTime()
	{
		startTime = System.currentTimeMillis();
	}
	
	private long countTime()
	{
		return System.currentTimeMillis() - startTime;
	}
}